﻿using AutoMapper;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Volo.Abp;
using Volo.Abp.Application.Services;
using Volo.Abp.DependencyInjection;
using Volo.Abp.Domain.Repositories;
using Volo.Abp.Linq;
using YaAppoint.Common;
using YaAppoint.DeviceTypes;
using YaAppoint.Response;

namespace YaAppoint.DepartmentDeviceTypes
{
    [RemoteService(isEnabled: false)]
    public class DepartmentDeviceTypeAppService(IRepository<Department, Guid> depatmentRepository,
                                                IRepository<DeviceType, Guid> deviceTypeRepository,
                                                IMapper mapper,
                                                ICommonAppService commonAppService,
                                                AsyncQueryableExecuter queryableExecuter) : ApplicationService, IDepartmentDeviceTypeAppService, ITransientDependency
    {
        private readonly IRepository<Department, Guid> _depatmentRepository = depatmentRepository;
        private readonly IRepository<DeviceType, Guid> _deviceTypeRepository = deviceTypeRepository;
        private readonly IMapper _mapper = mapper;
        private readonly AsyncQueryableExecuter _queryableExecuter = queryableExecuter;
        private readonly ICommonAppService _commonAppService = commonAppService;

        /// <summary>
        /// 获取到诊模式选项
        /// </summary>
        public BackJson LoadCheckInModeOptions()
        {
            var data = new List<object>();
            foreach (var val in Enum.GetValues(typeof(DeviceStatus)))
            {
                var option = new
                {
                    label = _commonAppService.GetEnumValueDescription(val),
                    value = Convert.ToInt32(val)
                };

                data.Add(option);
            }
            return new BackJson()
            {
                code=0,
                data = data
            };
        }

        /// <summary>
        ///  获取科室设备类型列表
        /// </summary>
        public async Task<BackJson> GetDepDeviceTypes(Guid id, string? filterName, int page, int pageSize)
        {
            var dep = await _depatmentRepository.FirstOrDefaultAsync(x => x.Id == id);
            if (dep == null)
            {
                throw new BusinessException(CustomErrorCodes.DepartmentNotExist);
            }
            var deviceTypes = dep.DeviceTypes;
            if (deviceTypes == null)
            { 
                deviceTypes = new List<DeviceType>();
            }
            if (!string.IsNullOrEmpty(filterName))
            {
                deviceTypes = deviceTypes.Where(d => d.Name.Contains(filterName)).ToList();
            }
            var total =  deviceTypes.Count;
            deviceTypes = deviceTypes.Skip(pageSize * (page - 1)).Take(pageSize).ToList();
            return new BackJson()
            {
                code = 0,
                data = new { 
                    deviceTypes = _mapper.Map<List<DeviceType>, List<DeviceTypeDto>>(deviceTypes),
                    totalCount = total
                }
            };
        }


        /// <summary>
        /// 系统设备类型列表(可添加的)
        /// </summary>
        public async Task<BackJson> GetSystemDeviceTypes(Guid depId, string? filterName, int page, int pageSize)
        {
            var query = await _deviceTypeRepository.GetQueryableAsync();
            if (!string.IsNullOrEmpty(filterName))
            {
                query = query.Where(x => x.Name.Contains(filterName));
            }
            var list = await _queryableExecuter.ToListAsync(query);
            var department = await _depatmentRepository.FirstOrDefaultAsync(x => x.Id == depId);
            var deviceTypeList = new List<DeviceType>();
            if (department == null)
            {
                throw new BusinessException(CustomErrorCodes.DepartmentNotExist);
            }
            foreach (var item in list)
            {
                var departDeviceType = department.DeviceTypes!.FirstOrDefault(x=>x.Id==item.Id);
                if (departDeviceType == null)
                {
                    deviceTypeList.Add(item);
                }
            }

            var total = deviceTypeList.Count;
            deviceTypeList = deviceTypeList.Skip(pageSize * (page - 1)).Take(pageSize).ToList();
            var dts = _mapper.Map<List<DeviceType>, List<DeviceTypeDto>>(deviceTypeList);
            return new BackJson()
            {
                code = 0,
                data = new
                { 
                    deviceTypes= dts,
                    totalCount =total
                }
            };
        }

        /// <summary>
        /// 提交新建
        /// </summary>
        public async Task<BackJson> SubmitCreate(CreateDeviceTypeDto dto, Guid depId)
        {
            var dep = await _depatmentRepository.FirstOrDefaultAsync(x => x.Id == depId);
            if (dep == null)
            {
                throw new BusinessException(CustomErrorCodes.DepartmentNotExist);
            }

            var deviceType = _mapper.Map<CreateDeviceTypeDto, DeviceType>(dto);
            await _deviceTypeRepository.InsertAsync(deviceType);
            if (dep.DeviceTypes == null)
            {
                dep.DeviceTypes = new List<DeviceType>();
            }
            dep.DeviceTypes.Add(deviceType);
            return new BackJson()
            {
                code = 0,
                msg = "设备类型创建成功，并以被添加到当前科室"
            };
        }

        /// <summary>
        /// 移除多个
        /// </summary>
        public async Task<BackJson> RemoveMany(List<DeviceTypeDto> dtoList, Guid depId)
        {
            var dep = await _depatmentRepository.FirstOrDefaultAsync(x => x.Id == depId);
            if (dep == null)
            {
                throw new BusinessException(CustomErrorCodes.DepartmentNotExist);
            }

            foreach (var item in dtoList)
            {
                var deviceType = await _deviceTypeRepository.FirstOrDefaultAsync(x => x.Id == item.Id);
                if (deviceType == null)
                {
                    continue;
                }
                else
                { 
                    dep.DeviceTypes.Remove(deviceType);
                }
            }

            return new BackJson()
            {
                code = 0,
                msg = "移除成功。"
            };
        }


        /// <summary>
        /// 移除单个
        /// </summary>
        public async Task<BackJson> RemoveSingle(Guid deviceTypeId, Guid depId)
        {
            var dep = await _depatmentRepository.FirstOrDefaultAsync(x => x.Id == depId);
            if (dep == null)
            {
                throw new BusinessException(CustomErrorCodes.DepartmentNotExist);
            }
            var deviceType = await _deviceTypeRepository.FirstOrDefaultAsync(x => x.Id == deviceTypeId);
            if (deviceType == null)
            {
                throw new BusinessException(CustomErrorCodes.DeviceTypeNotExist);
            }
            dep.DeviceTypes.Remove(deviceType);
            return new BackJson()
            {
                code = 0,
                msg = "移除成功。"
            };
        }

        /// <summary>
        /// 向科室添加设备类型
        /// </summary>
        public async Task<BackJson> AddDeviceTypeToDepartment(List<DeviceTypeDto> dtoList, Guid depId)
        {
            var deviceTypes = _mapper.Map<List<DeviceTypeDto>, List<DeviceType>>(dtoList);
            var dep = await _depatmentRepository.FirstOrDefaultAsync(x => x.Id == depId);
            if (dep == null)
            {
                throw new BusinessException(CustomErrorCodes.DepartmentNotExist);
            }
            if (dep.DeviceTypes == null) 
            {
                dep.DeviceTypes = new List<DeviceType>();
            }
            foreach (var item in deviceTypes)
            {
                var deviceType = await _deviceTypeRepository.FirstOrDefaultAsync(x => x.Id == item.Id);
                if (deviceType == null)
                {
                    throw new BusinessException(CustomErrorCodes.DeviceTypeNotExist);
                }
                dep.DeviceTypes.Add(deviceType);
            }
            return new BackJson()
            {
                code = 0,
                msg = "添加成功。"
            };
        }
    }
}
